/*
 * Created on 2005-2-17
 *
 */
package bma.common.langutil.core;

import java.util.ArrayList;
import java.util.Iterator;
import java.util.LinkedList;
import java.util.List;

/**
 * @author 关中
 * @since 1.0 (imported from BMA.ESP Project)
 * 
 */
public class ObjectPairCollection<VC, AC> {

	private List<ObjectPair<VC, AC>> objectPairs;

	private ObjectPairCollection<VC, AC> defaults;

	public ObjectPairCollection() {
		super();
		objectPairs = new LinkedList<ObjectPair<VC, AC>>();
	}

	public ObjectPairCollection(List<ObjectPair<VC, AC>> attr) {
		super();
		objectPairs = attr;
	}

	public List<ObjectPair<VC, AC>> getObjectPairs() {
		return objectPairs;
	}

	public void setDefaults(ObjectPairCollection<VC, AC> defaults) {
		this.defaults = defaults;
	}

	public void clear() {
		objectPairs.clear();
	}

	public boolean containAttribute(AC att) {
		Iterator<ObjectPair<VC, AC>> it = objectPairs.iterator();
		while (it.hasNext()) {
			ObjectPair<VC, AC> nv = it.next();
			if (nv.sameAttribute(att)) {
				return true;
			}
		}
		return defaults == null ? false : defaults.containAttribute(att);
	}

	public boolean containValue(VC value) {
		Iterator<ObjectPair<VC, AC>> it = objectPairs.iterator();
		while (it.hasNext()) {
			ObjectPair<VC, AC> nv = it.next();
			return nv.sameValue(value);
		}
		return defaults == null ? false : defaults.containValue(value);
	}

	public VC getByAttribute(AC key) {
		for (ObjectPair<VC, AC> nv : objectPairs) {
			if (nv.sameAttribute(key)) {
				return nv.getValue();
			}
		}
		return defaults == null ? null : defaults.getByAttribute(key);
	}

	public void setByAttribute(VC value, AC key) {
		for (ObjectPair<VC, AC> nv : objectPairs) {
			if (nv.sameAttribute(key)) {
				nv.setValue(value);
				return;
			}
		}
		add(value, key);
	}

	public AC getByValue(VC key) {
		for (ObjectPair<VC, AC> nv : objectPairs) {
			if (nv.sameValue(key)) {
				return nv.getAttribute();
			}
		}
		return defaults == null ? null : defaults.getByValue(key);
	}

	public void setByValue(VC key, AC attribute) {
		for (ObjectPair<VC, AC> nv : objectPairs) {
			if (nv.sameValue(key)) {
				nv.setAttribute(attribute);
				return;
			}
		}
		add(key, attribute);
	}

	public void add(VC value, AC attribute) {
		ObjectPair<VC, AC> nv = new ObjectPair<VC, AC>(value, attribute);
		objectPairs.add(nv);
	}

	public void removeAttribute(AC key) {
		Iterator<ObjectPair<VC, AC>> it = objectPairs.iterator();
		while (it.hasNext()) {
			ObjectPair<VC, AC> nv = it.next();
			if (nv.sameAttribute(key)) {
				it.remove();
			}
		}
	}

	public void removeValue(VC key) {
		Iterator<ObjectPair<VC, AC>> it = objectPairs.iterator();
		while (it.hasNext()) {
			ObjectPair<VC, AC> nv = it.next();
			if (nv.sameValue(key)) {
				it.remove();
			}
		}
	}

	public List<AC> listAllAttribute() {

		ArrayList<AC> r = new ArrayList<AC>(objectPairs.size());

		for (ObjectPair<VC, AC> nv : objectPairs) {
			r.add(nv.getAttribute());
		}
		return r;
	}

	public List<VC> listAllValue() {

		ArrayList<VC> r = new ArrayList<VC>(objectPairs.size());

		for (ObjectPair<VC, AC> nv : objectPairs) {
			r.add(nv.getValue());
		}
		return r;
	}

	public int size() {
		return this.objectPairs.size();
	}
}